#include <stdio.h>
#include <string.h>

#include <errno.h>

#define __USE_GNU // for pthread_setname_np()

#include "jthreads.h"

int init_handle_threads(short thread_num, handle_thread_t *handle_threads, void *(*start_fn)(void *), int epfd)
{
	for (int i = 0; i < thread_num; i++)
	{
		handle_thread_t *ht = (handle_threads + i);
		memset(ht, 0, sizeof(handle_thread_t));

		ht->epfd = epfd;

		int pr = pthread_create(&(ht->thread), NULL, start_fn, ht);
		if (pr != 0)
		{
			fprintf(stderr, "Unable to create handle thread, %d.", pr);
			return -1;
		}
		char pn[16] = {0};
		sprintf(pn, "jshandle %d", i);
		pthread_setname_np(ht->thread, pn);
	}

	return thread_num;
}

int init_accept_threads(short thread_num, accept_thread_t *accept_threads, void *(*start_fn)(void *), int socket_epfd, int handle_epfd)
{
	for (int i = 0; i < thread_num; i++)
	{
		accept_thread_t *at = (accept_threads + i);
		memset(at, 0, sizeof(accept_thread_t));

		at->socket_epfd = socket_epfd;
		at->handle_epfd = handle_epfd;

		int pr = pthread_create(&(at->thread), NULL, start_fn, at);
		if (pr != 0)
		{
			fprintf(stderr, "Unable to create accept thread, %d.", pr);
			return -1;
		}
		char pn[16] = {0};
		sprintf(pn, "jsaccept %d", i);
		pthread_setname_np(at->thread, pn);
	}

	return thread_num;
}

int init_output_threads(short thread_num, output_thread_t *output_threads, void *(*start_fn)(void *), enum output_type output_type, int output_fd)
{
	for (int i = 0; i < thread_num; i++)
	{
		output_thread_t *ot = (output_threads + i);
		memset(ot, 0, sizeof(output_thread_t));

		pthread_cond_init(&(ot->waiting_new_mail), NULL);
		pthread_mutex_init(&(ot->working_new_mail), NULL);

		q_init(&(ot->output_mail_queue));

		ot->output_type = output_type;
		ot->output_fd = output_fd;

		int pr = pthread_create(&(ot->thread), NULL, start_fn, ot);
		if (pr != 0)
		{
			fprintf(stderr, "Unable to create output thread, %d.", pr);
			return -1;
		}
		char pn[16] = {0};
		sprintf(pn, "jsoutput %d", i);
		pthread_setname_np(ot->thread, pn);
	}

	return thread_num;
}
